﻿#pragma once

#include "../util/object_pool.hh"
#include <curl/curl.h>
#include <fstream>
#include <cstdio>

namespace kratos {
namespace service {

class ScopeCurl {
private:
  constexpr static std::size_t BUFFER_LENGTH =
      1024 * 1024;      ///< 默认CURL缓冲区最大长度
  CURL *curl_{nullptr}; ///< CURL实例
  unique_pool_ptr<char> buffer_{
      kratos::make_unique_pool_ptr<char>(BUFFER_LENGTH)}; ///< 缓冲区指针
  std::size_t max_buffer_len_{BUFFER_LENGTH}; ///< 当前缓冲区最大长度
  std::size_t buffer_len_{0};                 ///< 缓冲区已使用长度

public:
  ScopeCurl();
 ~ScopeCurl();
  operator bool() { return (curl_ != nullptr); }
  // 获取CURL实例
  CURL *get() const;
  // 获取返回的数据指针
  const char *get_content() const;
  // 获取返回的数据长度
  size_t get_content_size() const;
  // 判空
  // 将获取的数据写入std::string
  auto to_string(std::string &s) -> bool;
  // 将返回的数据写入std::ostream
  auto to_stream(std::ostream &os) -> bool;
  auto to_stream(std::FILE *fp) -> bool;
  // 进行一次CURL调用
  // @param url 远程URL
  auto perform(const std::string &url) -> bool;
  // 设置CURL参数
  auto init_curl(const std::string &url) -> void;
  // 写入数据到缓冲区
  // @param data 数据指针
  // @param size 数据长度
  auto write(const char *data, size_t size) -> void;
  // CURL写入数据回调
  static size_t curl_write_fn(void *contents, size_t size, size_t nmemb,
                              void *userp);
};

} // namespace service
} // namespace kratos
